package cn.agiledata.bank.common.util;

import java.io.InputStream;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.net.URL;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

import javax.servlet.http.HttpServletRequest;

import org.apache.struts.action.ActionMapping;

import cn.agiledata.bank.account.service.AccountSummary;
import cn.agiledata.bank.account.service.IAccountService;
import cn.agiledata.bank.common.exception.BusinessException;
import cn.agiledata.bank.common.servlet.InitForString;
import cn.agiledata.bank.hibernateBean.Account;
import cn.agiledata.bank.hibernateBean.Operator;
import cn.agiledata.bank.hibernateBean.Sysbook;
import cn.agiledata.bank.hibernateBean.SysbookId;
import cn.agiledata.bank.hibernateBean.Transaction;
import com.vnv.infrastructure.logic.IPBMgrFactory;

public class WeatherUtil {

    /**
     * author joe date 2006-03-28 利用反射添加obj中的四个方法，因为都是通用方法，所以进行
     * 数据插入的时候统一调用此方法进行封装
     * 
     * @param obj
     *            需要插入值得bean
     * @param createOrUpdateUser
     *            需要插入的创建用户或者修改用户
     * 
     * DEMO：fillCreateAndUpdateInfo(Account,"7")
     * means:将Account中的setCreateTime，setUpdateTime，置为当前日期
     * 将setCreateUser，setUpdateUser置为7
     */
    public static void fillCreateAndUpdateInfo(Object obj,
            String createOrUpdateUser) {
        Method[] methods = obj.getClass().getMethods();
        for (int i = 0; i < methods.length; i++) {
            Method method = methods[i];
            try {
                if (method.getName().equals("setCreateTime")
                        || method.getName().equals("setUpdateTime")) {
                    method.invoke(obj, new Object[] { new Date() });
                }
                if (method.getName().equals("setCreateUser")
                        || method.getName().equals("setUpdateUser")) {
                    method.invoke(obj, new Object[] { createOrUpdateUser });
                }
            } catch (IllegalArgumentException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            } catch (IllegalAccessException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            } catch (InvocationTargetException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        }
    }
    
    public static void fillUpdateInfo(Object obj,
            String createOrUpdateUser) {
        Method[] methods = obj.getClass().getMethods();
        for (int i = 0; i < methods.length; i++) {
            Method method = methods[i];
            try {
                if (method.getName().equals("setUpdateTime")) {
                    method.invoke(obj, new Object[] { new Date() });
                }
                if (method.getName().equals("setUpdateUser")) {
                    method.invoke(obj, new Object[] { createOrUpdateUser });
                }
            } catch (IllegalArgumentException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            } catch (IllegalAccessException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            } catch (InvocationTargetException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        }
    }

    public static void cleanForm(Object cleanedForm) {
        Object[] fields = ArrayUtils.compositeArrays(new Object[] {
                cleanedForm.getClass().getFields(),
                cleanedForm.getClass().getDeclaredFields() });

        for (int i = 0; i < fields.length; i++) {
            Field field = (Field) fields[i];
            if (!field.getName().equals("errorMsg")) {
                try {
                    Method m = cleanedForm.getClass().getMethod(
                            getSetterName(field.getName()),
                            getTypes(field.getType().getName()));
                    if (!"[Ljava.lang.String;"
                            .equals(field.getType().getName()))
                        m.invoke(cleanedForm,
                                getArgs(field.getType().getName()));

                } catch (SecurityException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                } catch (NoSuchMethodException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                } catch (ClassNotFoundException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                } catch (Exception e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
            }
        }
    }

    private static Object[] getArgs(String type) throws Exception {
        if (type.equals("java.lang.String")) {
            return new Object[] { new String("") };
        } else if (type.equals("int")) {
            return new Object[] { new Integer(0) };
        } else if (type.equals("boolean")) {
            return new Object[] { new Boolean(false) };
        } else if (type.equals("long")) {
            return new Object[] { new Long(0) };
        } else if (type.equals("float")) {
            return new Object[] { new Float(0) };
        } else if (type.equals("double")) {
            return new Object[] { new Double(0) };
        } else {
            return new Object[] { Class.forName(type).newInstance() };
        }
    }

    private static String getSetterName(String propName) {
        return "set" + propName.substring(0, 1).toUpperCase()
                + propName.substring(1, propName.length());
    }

    private static Class[] getTypes(String type) throws ClassNotFoundException {
        if (type.equals("java.lang.String")) {
            return new Class[] { String.class };
        } else if (type.equals("int")) {
            return new Class[] { Integer.TYPE };
        } else if (type.equals("long")) {
            return new Class[] { Long.TYPE };
        } else if (type.equals("boolean")) {
            return new Class[] { Boolean.TYPE };
        } else if (type.equals("float")) {
            return new Class[] { Float.TYPE };
        } else if (type.equals("double")) {
            return new Class[] { Double.TYPE };
        } else {
            return new Class[] { Class.forName(type) };
        }
    }

    public static List getTradeType() {
        List tradeType = (List) InitForString.dataDictMap.get("TRADE_TYPE");
        Sysbook sysbook = new Sysbook();
        sysbook.setListName("-----------------------------------------------");
        sysbook.setId(new SysbookId());
        List result = new ArrayList();
        result.add(sysbook);
        result.addAll(tradeType);
        return result;
    }

    public static Account getAccountByEmail(String email) {
        Account acco = null;

        try {
            IAccountService accountService = (IAccountService) IPBMgrFactory
                    .getMgr("accountService");
            acco = accountService.findAccountByEmail(email);
        } catch (BusinessException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        return acco;
    }
    
    public static Account getAccountByMobile(String mobile) {
        Account acco = null;

        try {
            IAccountService accountService = (IAccountService) IPBMgrFactory
                    .getMgr("accountService");
            acco = accountService.findAccountByMobile(mobile);
        } catch (BusinessException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        return acco;
    }

    public static Account getAccountByEmailAvaible(String email) {
        Account acco = null;

        try {
            IAccountService accountService = (IAccountService) IPBMgrFactory
                    .getMgr("accountService");
            acco = accountService.findAccountByEmailAvaible(email);
        } catch (BusinessException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        return acco;
    }

    public static String getStrFromUrl(String url) {
        StringBuffer sb = new StringBuffer();
        try {
            URL u = new URL(url);
            InputStream in = u.openStream();
            byte[] bt = new byte[4096];
            int len = 0;
            while ((len = in.read(bt)) != -1) {
                sb.append(new String(bt, 0, len));
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return sb.toString();
    }

    public static AccountSummary getLoingInfoFromSession(
            HttpServletRequest request) {
        AccountSummary as = (AccountSummary) request.getSession().getAttribute(
                Constant.SESSION_ACCOUNT_SUMMARY);
        return as;
    }

    public static long getAccountIdFromSession(HttpServletRequest request) {
        long accountId = 0;
        AccountSummary as = getLoingInfoFromSession(request);
        if (as != null) {
            accountId = as.getAccountId();
        }
        return accountId;
    }

    public static String getAccountNameFromSession(HttpServletRequest request) {
        String accountName = null;
        AccountSummary as = getLoingInfoFromSession(request);
        if (as != null) {
            accountName = as.getAccountName();
        }
        return accountName;
    }

    public static long getSubAccountIdFromSession(HttpServletRequest request) {
        long accountId = 0;
        AccountSummary as = getLoingInfoFromSession(request);
        if (as != null) {
            accountId = as.getSelectedSubAccountId();
        }
        return accountId;
    }

    public static String getRootFromSession(HttpServletRequest request) {
        String root = "";
        AccountSummary as = getLoingInfoFromSession(request);
        if (as != null) {
            root = as.getRoot();
        }
        return root;
    }

    public static String getAccountIdFromUrl(String requestUri) {
        int prefixPos = requestUri.indexOf("/pay:");
        int startPos = prefixPos + 5;
        String url = requestUri.substring(startPos);
        int endPos = url.indexOf(":");
        return url.substring(0, endPos);
    }

    public static void main(String args[]) {
        Transaction tran = new Transaction();
        fillCreateAndUpdateInfo(tran, "joe");
    }

    public static Operator getOperator(HttpServletRequest request) {
        AccountSummary user = getLoingInfoFromSession(request);
        if (user.getOperatorCode() != null) {
            return user.getOperatorByIdInstance(user.getOperatorCode()
                    .toString());
        } else {
            return null;
        }
    }

    /**
     * 判断session是否已经超时过期
     */
    public static boolean sessionIsTimeout(HttpServletRequest request) {
        return getLoingInfoFromSession(request) == null;
    }

    /**
     * 根据账户得到email或者手机号码
     * 
     * @param a
     * @return
     */
    public static String getEmailOrMobileByAccount(Account a) {
        return a.getEmail() == null ? a.getMobile() : a.getEmail();
    }

    /**
     * 
     * @param a
     * @return
     */
    public static String getNameOrEmailOrMobileByAccount(Account a) {
        if (a == null) {
            return "";
        }
        if (!StringUtil.isStrEmpty(a.getName())) {
            return a.getName();
        } else {
            // if(StringUtil.isStrEmpty(a.getEmail())) {
            // return a.getMobile();
            // } else {
            // return a.getEmail();
            // }
            if (a.getEmStatus().equals(Constant.ACCOUNT_STATE_NORMAL)) {
                return a.getEmail();
            }
            if (a.getMobStatus().equals(Constant.ACCOUNT_STATE_NORMAL)) {
                return a.getMobile();
            }
            return "";
        }
    }

    public static void setPageModual(ActionMapping mapping,
            HttpServletRequest request) {
        String prefix = mapping.getModuleConfig().getPrefix();
        if (prefix.equals("/page/myspace")) {
            WebUtil.setSessionString(request, "modual", "space");
        }
        if (prefix.equals("/page/audit")) {
            WebUtil.setSessionString(request, "modual", "space");
        }
    }

}